/**************************************************************************
 * ports:
 *  VL_IN8(&clk,0,0);
 *  VL_IN8(&rstn,0,0);
 *  VL_IN8(&ena,0,0);
 *  VL_OUT8(&beep,0,0);
***************************************************************************/

#include <stdlib.h>
#include <iostream>
#include <verilated.h>
#include <verilated_vcd_c.h>
#include "Vbuzzer.h"
#include "Vbuzzer___024root.h"

#define PERIOD 2
#define MAX_TIME 1000000
vluint64_t sim_time = 0;

void reset(Vbuzzer*, int);
void neg_edge_eval(Vbuzzer*);
void pos_edge_eval(Vbuzzer*);

int main(int argc, char **argv) {
	Vbuzzer* dut = new Vbuzzer;

	Verilated::traceEverOn(true);
	VerilatedVcdC *m_trace = new VerilatedVcdC;
	dut->trace(m_trace, 2);
	m_trace->open("waveform.vcd");


	while(sim_time < MAX_TIME) {

		reset(dut, int(1.5*PERIOD));

		if(sim_time < 50*PERIOD) {
			dut->ena = 0;
		} else {
			dut->ena = 1;
		}
		
		if(sim_time % PERIOD == 0) {
			pos_edge_eval(dut);
			m_trace->dump(sim_time);
			neg_edge_eval(dut);
		}

		if((sim_time % PERIOD) - 1 == 0) {
			neg_edge_eval(dut);
			m_trace->dump(sim_time);
			pos_edge_eval(dut);
		}

		sim_time++;
	}
	dut->final();
	m_trace->close();

	delete dut;
}

void reset(Vbuzzer* dut, int n) {
  if(sim_time < n) {
    dut->rstn = 0;
  } else {
    dut->rstn = 1;
  }
}

void neg_edge_eval(Vbuzzer* dut) {
	dut->clk = 0;
	dut->eval();
}

void pos_edge_eval(Vbuzzer* dut) {
	dut->clk = 1;
	dut->eval();
}
